package com.googlecode.sparda.commons.util;


/**
 * This class provide an utility for percentage calculus.
 * @author Fabio Grucci (<i>alias</i> <b>Phoenix</b>)
 *
 */
public class Percentager {
	/**
	 * The percentage string format.
	 */
	private final PercentageFormat percentageFormat;
	/**
	 * The total step count.
	 */
	private final int totalStepCount;
	/**
	 * The current step.
	 */
	private int currentStep;
	/**
	 * The operation name.
	 */
	private final String operationName;
	/**
	 * Build a percentage calculator whit a totalStepCount.
	 * @param totalStepCount The total number of step
	 */
	public Percentager(int totalStepCount) {
		this("Operation", totalStepCount);
	}
	/**
	 * Build a percentage calculator whit a totalStepCount and an operation name.
	 * @param operationName The operation name object of the percentage
	 * @param totalStepCount The total number of step
	 */
	public Percentager(String operationName, int totalStepCount) {
		this(operationName, totalStepCount, true);
	}
	/**
	 * Build a percentage calculator whit a totalStepCount an operation name specifying a formatting style.
	 * @param operationName The operation name object of the percentage
	 * @param totalStepCount The total number of step
	 * @param decimalWhitZero A boolean <code>true</code> if want 0 based percentage format, <code>false</code> otherwise
	 */
	public Percentager(String operationName, int totalStepCount, boolean decimalWhitZero) {
		this(operationName, totalStepCount, decimalWhitZero ? buildDefaultDecimalFormatString(totalStepCount) : "#");
	}
	/**
	 * Build a percentage calculator for an operation whit a totalStepCount and a decimal format.
	 * @param operationName The operation name object of the percentage
	 * @param totalStepCount The total number of step
	 * @param decimalFormat The decimal format of the partial
	 */
	private Percentager(String operationName, int totalStepCount, String decimalFormat) {
		this(operationName, totalStepCount, new SimplePercentageFormat());
	}
	/**
	 * Build a percentage calculator whit a totalStepCount and a percentage format.
	 * @param totalStepCount The total number of step
	 * @param percentageFormat The output string formatter of the percentage format
	 */
	public Percentager(String operationName, int totalStepCount, PercentageFormat percentageFormat) {
		this.operationName = operationName;
		this.totalStepCount = totalStepCount;
		this.percentageFormat = percentageFormat;
	}
	
	/**
	 * Called to notify the ended of one step.
	 * @return The current percentage
	 */
	public double next() {
		++this.currentStep;
		return this.getPercentage();
	}
	/**
	 * Return the current percentage value. 
	 * @return The current percentage
	 */
	public double getPercentage() {
		return (double) currentStep/totalStepCount;
	}
	/**
	 * Return the total number of step to do.
	 * @return The total number of step
	 */
	public int getTotalStepCount() {
		return this.totalStepCount;
	}
	/*
	 * (non-Javadoc)
	 * @see java.lang.Object#toString()
	 */
	@Override
	public String toString() {
		return this.operationName + " at " + this.percentageFormat.format(this.getPercentage(), this.currentStep, this.totalStepCount);
	}
	/**
	 * Method that build the default decimal format string.
	 * @param totalStepCount The total step count
	 * @return The default decimal format string
	 */
	private static String buildDefaultDecimalFormatString(int totalStepCount) {
		StringBuilder s = new StringBuilder();
		for(int i=0; i<=Math.log10(totalStepCount); i++)
			s.append("0");
		return s.toString();
	}
	
}
